
package com.tenentia.pcmps.swm.business.implementation;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;

import org.apache.log4j.Logger;

import com.liferay.portal.model.User;
import com.liferay.portal.service.UserLocalServiceUtil;
import com.tenentia.pcmps.swm.Constants;
import com.tenentia.pcmps.swm.business.BusinessLogicException;
import com.tenentia.pcmps.swm.business.interfaces.UsersManager;
import com.tenentia.pcmps.swm.data.DataAccessObjectsFactory;
import com.tenentia.pcmps.swm.data.beans.ApplicationUser;
import com.tenentia.pcmps.swm.data.beans.UserRole;
import com.tenentia.pcmps.swm.data.beans.UsersGroup;
import com.tenentia.pcmps.swm.data.interfaces.GroupsDAO;
import com.tenentia.pcmps.swm.data.interfaces.RolesDAO;
import com.tenentia.pcmps.swm.util.ApplicationProperties;

/**
 * 
 * @author tEnEntia, S.L.N.E.
 * 
 */
public class UsersManagerImpl implements UsersManager {

	private static final Logger LOGGER = Logger.getLogger(UsersManagerImpl.class.getPackage().getName());

	UsersManagerImpl() {

		super();
	}

	@Override
	public void delete(ApplicationUser user) throws BusinessLogicException {

		// TODO Auto-generated method stub

	}

	@Override
	public ApplicationUser get(ApplicationUser user) throws BusinessLogicException {

		try {
			User tmpUser = UserLocalServiceUtil.getUser(user.getInternalID());

			LOGGER.debug("tmpUser: " + tmpUser);

			user.setActive(tmpUser.isActive());
			user.setFirstName(tmpUser.getFirstName());
			user.setLastName(tmpUser.getLastName());
			user.setElectronicMailAddress(tmpUser.getEmailAddress());
			user.setGender(String.valueOf(tmpUser.isMale() ? 'M' : 'F'));
			user.setBirthDate(tmpUser.getBirthday());
			user.setUserID(tmpUser.getScreenName());

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);

			try {
				UserRole userRole = rolesDAO.getUserRole(user);
				user.setRole(userRole);
			} catch (Exception e) {
				LOGGER.debug(e, e);
				user.setRole(new UserRole());
			}

			GroupsDAO groupsDAO = (GroupsDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.GROUPS_DAO);

			try {
				user.setGroup(groupsDAO.getUserGroup(user));
			} catch (Exception e) {
				LOGGER.debug(e, e);
				user.setGroup(new UsersGroup());
			}

			return user;
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}

	}

	@Override
	public List<ApplicationUser> getAvailableMediatorUsers() throws BusinessLogicException {

		try {

			Long organizationID = Long.valueOf(ApplicationProperties.getInstance().getProperty("organizationID"));

			List<User> organizationUsers = UserLocalServiceUtil.getOrganizationUsers(organizationID);
			List<ApplicationUser> tmpList = new ArrayList<ApplicationUser>();

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);

			for (Iterator<User> iterator = organizationUsers.iterator(); iterator.hasNext();) {
				User user = iterator.next();
				try {
					ApplicationUser tmpApplicationUser = new ApplicationUser();
					tmpApplicationUser.setInternalID(user.getUserId());
					UserRole userRole = rolesDAO.getUserRole(tmpApplicationUser);
					if (null != userRole && null != userRole.getInternalID() && userRole.getInternalID().equals(UserRole.MEDIATOR)) {
						tmpApplicationUser.setFirstName(user.getFirstName());
						tmpApplicationUser.setLastName(user.getLastName());
						tmpApplicationUser.setElectronicMailAddress(user.getEmailAddress());
						tmpApplicationUser.setActive(user.isActive());
						tmpApplicationUser.setRole(userRole);
						tmpList.add(tmpApplicationUser);
					}
				} catch (Exception e) {
					// TODO: handle exception
				}
			}

			return tmpList;
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}

	}

	@Override
	public List<ApplicationUser> getTableItemsByRange(Object filterParameters, Object sortParameters, Integer firstRow, Integer numberOfRows) throws BusinessLogicException {

		try {

			Long organizationID = Long.valueOf(ApplicationProperties.getInstance().getProperty("organizationID"));

			List<User> organizationUsers = UserLocalServiceUtil.getOrganizationUsers(organizationID);
			List<ApplicationUser> tmpList = new ArrayList<ApplicationUser>();
			List<ApplicationUser> methodResult = new ArrayList<ApplicationUser>();

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);

			for (Iterator<User> iterator = organizationUsers.iterator(); iterator.hasNext();) {
				User user = iterator.next();
				try {
					ApplicationUser tmpApplicationUser = new ApplicationUser();
					tmpApplicationUser.setInternalID(user.getUserId());
					UserRole userRole = rolesDAO.getUserRole(tmpApplicationUser);
					if (null != userRole) {
						tmpApplicationUser.setFirstName(user.getFirstName());
						tmpApplicationUser.setLastName(user.getLastName());
						tmpApplicationUser.setElectronicMailAddress(user.getEmailAddress());
						tmpApplicationUser.setActive(user.isActive());
						tmpApplicationUser.setRole(userRole);
						tmpList.add(tmpApplicationUser);
					}
				} catch (Exception e) {
					// TODO: handle exception
				}
			}

			int firstItem = firstRow.intValue();

			int lastItem = firstItem + numberOfRows.intValue();

			for (int i = firstItem; i < lastItem; i++) {
				try {

					ApplicationUser tmpApplicationUser = tmpList.get(i);
					methodResult.add(tmpApplicationUser);
				} catch (Exception e) {
					// TODO: handle exception
				}
			}

			return methodResult;
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}
	}

	@Override
	public Integer getTableRowCount(Object filterParameters) throws BusinessLogicException {

		try {

			Long organizationID = Long.valueOf(ApplicationProperties.getInstance().getProperty("organizationID"));

			List<User> organizationUsers = UserLocalServiceUtil.getOrganizationUsers(organizationID);
			List<ApplicationUser> tmpList = new ArrayList<ApplicationUser>();

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);

			for (Iterator<User> iterator = organizationUsers.iterator(); iterator.hasNext();) {
				User user = iterator.next();
				try {
					ApplicationUser tmpApplicationUser = new ApplicationUser();
					tmpApplicationUser.setInternalID(user.getUserId());
					UserRole userRole = rolesDAO.getUserRole(tmpApplicationUser);
					if (null != userRole) {
						tmpApplicationUser.setFirstName(user.getFirstName());
						tmpApplicationUser.setLastName(user.getLastName());
						tmpApplicationUser.setElectronicMailAddress(user.getEmailAddress());
						tmpApplicationUser.setActive(user.isActive());
						tmpApplicationUser.setRole(userRole);
						tmpList.add(tmpApplicationUser);
					}
				} catch (Exception e) {
					// TODO: handle exception
				}
			}

			return Integer.valueOf(tmpList.size());
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}

	}

	@Override
	public void save(User authenticatedUser, ApplicationUser newUser) throws BusinessLogicException {

		try {
			Locale defaultLocale = new Locale("es", "ES");

			GregorianCalendar tmpGregorianCalendar = new GregorianCalendar();
			tmpGregorianCalendar.setTime(newUser.getBirthDate());

			User tmpUser = UserLocalServiceUtil.addUser(authenticatedUser.getUserId(), //
					authenticatedUser.getCompanyId(), //
					false, //
					newUser.getPassword(), //
					newUser.getPassword(), //
					true, //
					Constants.STRING_EMPTY, //
					newUser.getElectronicMailAddress(), //
					Constants.STRING_EMPTY, //
					defaultLocale, //
					newUser.getFirstName(), //
					Constants.STRING_EMPTY, // , //
					newUser.getLastName(), //
					0, //
					0, //
					newUser.getGender().equals(String.valueOf('M')), //
					tmpGregorianCalendar.get(Calendar.MONTH) + 1, //
					tmpGregorianCalendar.get(Calendar.DATE), //
					tmpGregorianCalendar.get(Calendar.YEAR), //
					Constants.STRING_EMPTY, // , //
					authenticatedUser.getGroupIds(), //
					authenticatedUser.getOrganizationIds(), //
					authenticatedUser.getRoleIds(), //
					authenticatedUser.getUserGroupIds(), //
					false, //
					null //
					);

			UserLocalServiceUtil.updateAgreedToTermsOfUse(tmpUser.getUserId(), true);

			newUser.setInternalID(tmpUser.getUserId());

			Long organizationID = Long.valueOf(ApplicationProperties.getInstance().getProperty("organizationID"));

			long[] tmpLongArray = new long[] { newUser.getInternalID().longValue() };

			UserLocalServiceUtil.addOrganizationUsers(organizationID.longValue(), tmpLongArray);

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);
			newUser.setRole(rolesDAO.setUserRole(newUser));
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}

	}

	@Override
	public void update(ApplicationUser user) throws BusinessLogicException {

		try {

			User tmpUser = UserLocalServiceUtil.getUser(user.getInternalID());
			tmpUser.setActive(user.getActive());
			tmpUser.setFirstName(user.getFirstName());
			tmpUser.setLastName(user.getLastName());
			tmpUser.setEmailAddress(user.getElectronicMailAddress());
			tmpUser.setPassword(user.getPassword());
			tmpUser.setPasswordEncrypted(false);
			tmpUser.setPasswordModified(true);
			tmpUser.setPasswordModifiedDate(new Date());
			tmpUser.setPasswordUnencrypted(user.getPassword());
			UserLocalServiceUtil.updateUser(tmpUser);

			RolesDAO rolesDAO = (RolesDAO) DataAccessObjectsFactory.getInstance().createNewDataAccessObject(DataAccessObjectsFactory.ROLES_DAO);
			user.setRole(rolesDAO.setUserRole(user));
		} catch (Exception e) {
			LOGGER.error(e, e);
			throw new BusinessLogicException(e.getMessage());
		}

	}

}
